﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using Emgu.CV;
using Emgu.CV.Structure;
using Emgu.CV.CvEnum;
using System.IO;
using Newtonsoft.Json;

namespace FormMainSSID
{
    public partial class FormConfigEstablishDisplay : Form
    {
        public Form1 FormMainSSID = new Form1();
        public Layer layer = new Layer();
        public Layers dictlay = new Layers();
        public Offset offset = null;
        public move_data data;

        bool isReLoad = false;

        int rawWidth, rawHeight;

        string description = null;

        int dimensions;
        string[] size = new string[] { };

        List<bool> isexist = new List<bool>();
        
        string path_config = null;
        List<string> path_dimensions = new List<string>();
        int ceng, hang, lie;

        Image<Gray, byte> image = null;
        
        public FormConfigEstablishDisplay()
        {
            InitializeComponent();
        }

        private void textBoxDescription_TextChanged(object sender, EventArgs e)
        {
            description = textBoxDescription.Text;
            size = description.Split('/');
            dimensions = size.Length;
            labelbottomsize.Text = size[0];
            labeldimensions.Text = dimensions.ToString();
        }

        private void buttonRawPath_Click(object sender, EventArgs e)
        {
            FolderBrowserDialog fbd = new FolderBrowserDialog();
            if(fbd.ShowDialog() == DialogResult.OK)
            {
                FormMainSSID.path_raw = fbd.SelectedPath;
            }
            textBoxRawPath.Text = FormMainSSID.path_raw;
        }

        private void buttonPath_Click(object sender, EventArgs e)
        {
            FolderBrowserDialog fbd = new FolderBrowserDialog();
            if (fbd.ShowDialog() == DialogResult.OK)
            {
                path_config = fbd.SelectedPath;
                textBoxPath.Text = path_config;
            }
        }

        private void textBoxLayer_TextChanged(object sender, EventArgs e)
        {
            ceng = int.Parse(textBoxLayer.Text);
            if (isReLoad)
            {
                if (dictlay.dict_layer.ContainsKey(ceng))
                {
                    layer = dictlay.dict_layer[ceng];
                    textBoxHang.Text = layer.hang.ToString();
                    textBoxLie.Text = layer.lie.ToString();

                    textBoxDescription.Text = layer.description;
                    size = description.Split('/');
                    labelbottomsize.Text = layer.dimension[0];
                    labeldimensions.Text = layer.dimensions.ToString();

                    FormMainSSID.path_raw = layer.path_raw;
                    path_config = layer.path_config;
                    textBoxRawPath.Text = FormMainSSID.path_raw;
                    textBoxPath.Text = layer.path_config;
                }
            }
        }

        private void FormConfigEstablishDisplay_Load(object sender, EventArgs e)
        {
            if (FormMainSSID.path_config == null)
            {
                isReLoad = false;
                image = new Image<Gray, byte>(FormMainSSID.files[0]);
                RawWidth.Text = image.Width.ToString();
                RawHeigtht.Text = image.Height.ToString();
                rawWidth = image.Width;
                rawHeight = image.Height;
                dimensions = 3;
                description = "256/512/1024";
                textBoxDescription.Text = description;
                size = description.Split('/');
                labelbottomsize.Text = size[0];
                labeldimensions.Text = dimensions.ToString();
                textBoxRawPath.Text = FormMainSSID.path_raw;
                layer.dictdim = new List<Dictionary<Point, string>>();
            }
            else
            {
                isReLoad = true;
                dictlay = JsonConvert.DeserializeObject<Layers>(File.ReadAllText(FormMainSSID.path_config));
                var example = dictlay.dict_layer.ElementAt(0);
                layer = example.Value;
                rawWidth = rawHeight = layer.scale_raw;
                textBoxLayer.Text = layer.layer.ToString();
                ceng = layer.layer;

                hang = layer.hang;
                lie = layer.lie;
                dimensions = layer.dimensions;
                description = layer.description;

                textBoxLayer.Text = ceng.ToString();
                textBoxHang.Text = hang.ToString();
                textBoxLie.Text = lie.ToString();

                textBoxDescription.Text = description;
                size = description.Split('/');
                labelbottomsize.Text = size[0];
                labeldimensions.Text = dimensions.ToString();

                FormMainSSID.path_raw = layer.path_raw;
                path_config = layer.path_config;
                textBoxRawPath.Text = FormMainSSID.path_raw;
                textBoxPath.Text = path_config;

                FormMainSSID.files = Directory.GetFiles(FormMainSSID.path_raw);
                Array.Sort(FormMainSSID.files, delegate (string s1, string s2)
                {
                    return
                    ((int.Parse(s1.Split('_')[1]) * 10000 + int.Parse(s1.Split('_')[2]) * 100 + int.Parse(s1.Split('_')[3])).
                    CompareTo((int.Parse(s2.Split('_')[1]) * 10000 + int.Parse(s2.Split('_')[2]) * 100 + int.Parse(s2.Split('_')[3])))
                    );
                });
                image = new Image<Gray, byte>(FormMainSSID.files[0]);
            }
        }

        private void buttonOK_Click(object sender, EventArgs e)
        {
            Image<Gray, byte> snp = null;
            Image<Gray, byte> snp_resize = null;
            string[] name = null;
            System.Text.RegularExpressions.Regex rex =
                    new System.Text.RegularExpressions.Regex("^[0-9]+$");
            if (!rex.IsMatch(textBoxLayer.Text))
            {
                MessageBox.Show("选择层输入非数字", "错误提示", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            else if (!rex.IsMatch(textBoxHang.Text))
            {
                MessageBox.Show("一层行数输入非数字", "错误提示", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            else if (!rex.IsMatch(textBoxLie.Text))
            {
                MessageBox.Show("列数输入非数字", "错误提示", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            else if(!Directory.Exists(path_config))
            {
                MessageBox.Show("构造图像存储路径不存在", "错误提示", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            else
            {
                ceng = int.Parse(textBoxLayer.Text);
                hang = int.Parse(textBoxHang.Text);
                lie = int.Parse(textBoxLie.Text);
                progressBar.Maximum = hang * lie;

                layer.path_raw = FormMainSSID.path_raw;
                layer.path_config = path_config;
                layer.scale_raw = image.Width;
                layer.layer = ceng;
                layer.hang = hang;
                layer.lie = lie;
                layer.description = description;
                layer.dimensions = dimensions;
                layer.dimension = size;

                if (!isReLoad)
                {
                    if(Directory.Exists(path_config + "//Config.json"))
                    {
                        dictlay = JsonConvert.DeserializeObject<Layers>(File.ReadAllText(path_config + "//Config.json"));
                    }
                    else
                    {
                        dictlay.dict_layer = new Dictionary<int, Layer>();
                    }
                    for (int i = 0; i < dimensions; i++)
                    {
                        path_dimensions.Add(path_config + "//" + "snp_" + ceng.ToString() + "_" + size[i]);
                        //判断文件的存在
                        if (Directory.Exists(path_dimensions[i]) == false)//如果不存在就创建子图片文件夹
                        {
                            Directory.CreateDirectory(path_dimensions[i]);
                            isexist.Add(false);
                        }
                        else
                        {
                            isexist.Add(true);
                        }
                        Console.WriteLine(path_dimensions[i]);
                        layer.dictdim.Add(new Dictionary<Point, string>());
                    }

                    for (int i = 0; i < hang; i++)
                    {
                        for (int j = 0; j < lie; j++)
                        {
                            Point poi = new Point();

                            poi.X = i;
                            poi.Y = j;

                            Console.WriteLine(i.ToString() + ".." + j.ToString());
                            for (int t = 0; t < dimensions; t++)
                            {
                                //if (!isexist[t])
                                {
                                    //snp = new Image<Gray, byte>(FormMainSSID.files[i * lie + j + (ceng - 1) * hang * lie]);

                                    name = FormMainSSID.files[i * lie + j + (ceng - 1) * hang * lie].Split('\\');

                                    //snp_resize = snp.Resize(int.Parse(size[t]), int.Parse(size[t]), Inter.Cubic);
                                    //snp_resize.Save(path_dimensions[t] + "\\" + name[name.Length - 1]);
                                    layer.dictdim[t].Add(poi, path_dimensions[t] + "\\" + name[name.Length - 1]);
                                }
                            }
                            //snp_resize = snp.Resize(256, 256, Inter.Cubic);
                            //snp_resize.Save(path_256 + "\\" + name[name.Length - 1]);

                            //snp_resize = snp.Resize(512, 512, Inter.Cubic);
                            //snp_resize.Save(path_512 + "\\" + name[name.Length - 1]);

                            //snp_resize = snp.Resize(1024, 1024, Inter.Cubic);
                            //snp_resize.Save(path_1024 + "\\" + name[name.Length - 1]);

                            progressBar.Value = i * lie + j + 1;
                            Console.WriteLine(progressBar.Value.ToString());
                            //Console.WriteLine(path_256 + "\\" + name[name.Length - 1]);
                        }
                    }
                    offset = JsonConvert.DeserializeObject<Offset>(File.ReadAllText(path_config + "\\Jelly.aif.json"));
                    layer.Position = Calculate.CalPosition(offset, layer.layer);
                    data = Calculate.Puzzle(layer, int.Parse(layer.dimension[0]), new int[] { 0, 0 }, new int[] { layer.hang - 1, layer.lie - 1 });
                    data.img.Save(layer.path_config + "\\" + "fullsnp_" + layer.layer.ToString() + "_" + layer.dimension[0] + ".tif");
                    layer.pos = new int[2];
                    layer.pos[0] = data.x;
                    layer.pos[1] = data.y;
                    layer.path_fullsnp = layer.path_config + "\\" + "fullsnp_" + layer.layer.ToString() + "_" + layer.dimension[0] + ".tif";
                    FormMainSSID.snp = data.img;
                    if (dictlay.dict_layer.ContainsKey(ceng))
                    {
                        dictlay.dict_layer[ceng] = layer;
                    }
                    else
                    {
                        dictlay.dict_layer.Add(ceng, layer);
                    }
                    File.WriteAllText(layer.path_config + "\\" + "Config.json", JsonConvert.SerializeObject(dictlay));
                }
                else
                {
                    dictlay.dict_layer[layer.layer] = layer;
                    snp = new Image<Gray, byte>(layer.path_fullsnp);
                    FormMainSSID.snp = snp;
                    File.WriteAllText(layer.path_config + "\\" + "Config.json", JsonConvert.SerializeObject(dictlay));
                }
                FormMainSSID.layer = layer;
                this.Close();
            }
        }

        private void update()
        {
            ;
        }
    }
}
